package main

import (
	"flag"
	clientset "github.com/k8snetworkplumbingwg/network-attachment-definition-client/pkg/client/clientset/versioned"
	sharedInformers "github.com/k8snetworkplumbingwg/network-attachment-definition-client/pkg/client/informers/externalversions"
	log "github.com/sirupsen/logrus"
	"k8s.io/client-go/informers"
	"k8s.io/client-go/kubernetes"
	"k8s.io/client-go/tools/clientcmd"
	"netwatcher/watcher"
	"os"
	"os/signal"
	"time"
)

var (
	masterURL  string
	kubeconfigPath string
)

func main() {

	flag.StringVar(&masterURL, "master", "", "The address of the Kubernetes API server. Overrides any value in kubeconfig. Required if out-of-cluster.")
	flag.StringVar(&kubeconfigPath, "kubeconfig", "", "Path to a kubeconfig. Required if out-of-cluster.")
	flag.Parse()

	kubecfg, err := clientcmd.BuildConfigFromFlags(masterURL, kubeconfigPath)
	if err != nil {
		log.Fatalf("Error building kubeconfig: %s", err.Error())
		return
	}

	kubeClientSet, err := kubernetes.NewForConfig(kubecfg)
	if err != nil {
		log.Fatalf("error building kubernetes clientset: %s", err.Error())
		return
	}

	netAttachDefClientSet, err := clientset.NewForConfig(kubecfg)
	if err != nil {
		log.Fatalf("error creating net-attach-def clientset: %s", err.Error())
		return
	}

	kubeInformerFactory := informers.NewSharedInformerFactory(kubeClientSet, time.Second*30)
	netAttachDefFactory := sharedInformers.NewSharedInformerFactory(netAttachDefClientSet, time.Second*30)

	networkController := watcher.NewNetworkController(
		kubeClientSet,
		netAttachDefClientSet,
		netAttachDefFactory.K8sCniCncfIo().V1().NetworkAttachmentDefinitions(),
		kubeInformerFactory.Core().V1().Services(),
		kubeInformerFactory.Core().V1().Pods(),
		kubeInformerFactory.Core().V1().Endpoints(),
	)

	stopChan := make(chan struct{})
	c := make(chan os.Signal, 1)
	signal.Notify(c, os.Interrupt)
	go func() {
		<-c
		close(stopChan)
		<-c
		os.Exit(1)
	}()
	kubeInformerFactory.Start(stopChan)
	netAttachDefFactory.Start(stopChan)
	networkController.Run(stopChan)
}